#include "serverHead/head.h"
#include "serverHead/taskQueue.h"

int exitPipe[2];

void handler(int signum){
    printf("signum = %d\n", signum);
    write(exitPipe[1], "1", 1);
}

int main(int argc, char* argv[])
{   
    // ./server ../conf/server.conf
    ARGS_CHECK(argc, 2);

    int fd1 = open(argv[1], O_RDONLY);
    ERROR_CHECK(fd1, -1, "open file");

    char buf[1024] = {0};
    read(fd1, buf, sizeof(buf));
    const char *pIp;
    const char *pPort;
    const char *pNum;
    pIp = strtok(buf, " ");
    pPort = strtok(NULL, " ");
    pNum = strtok(NULL, " ");

    pipe(exitPipe);
   
    if(fork() != 0){
        printf("pid = %d\n", getpid());
        close(exitPipe[0]);
        signal(SIGUSR1, handler);
        wait(NULL);
        exit(0);
    }
    close(exitPipe[1]);

    threadPool_t threadPool;
    int workernum = atoi(pNum);
    threadPoolInit(&threadPool, workernum); //已完成

    makeWorker(&threadPool);    

    //tcp连接
    int sockfd;
    tcpInit(pIp, pPort, &sockfd);

    //监听
    int epfd = epoll_create(1);
    epollAdd(epfd, sockfd);
    epollAdd(epfd, exitPipe[0]);
    struct epoll_event readyset[2];

    train_t* train = (train_t*)calloc(1, sizeof(train_t));
    ERROR_CHECK(train, NULL, "calloc failed");

    while(1){
        int readynum = epoll_wait(epfd, readyset, 2, -1);
        for(int i = 0; i < readynum; ++i){
            if(readyset[i].data.fd == sockfd){
                bzero(train, sizeof(train_t));
                int netfd = accept(sockfd, NULL, NULL);
                printf("连接\n"); 
                recvTrain(netfd, train);
                if((train->order == ORDER_PUTS)||(train->order == ORDER_GETS)){
                    //长命令
                    pthread_mutex_lock(&threadPool.taskQueue.mutex);
                    taskEnQueue(&threadPool.taskQueue, netfd);
                    printf("main thread send a task\n");
                    pthread_cond_signal(&threadPool.taskQueue.cond);
                    pthread_mutex_unlock(&threadPool.taskQueue.mutex);
                }
                else{
                    shortCommandEvent(train, netfd);
                }
            }
            else if(readyset[i].data.fd == exitPipe[0]){
                printf("threadPool is going to exit\n");
                pthread_mutex_lock(&threadPool.taskQueue.mutex);
                threadPool.exitFlag = 1;
                pthread_cond_broadcast(&threadPool.taskQueue.cond);
                pthread_mutex_unlock(&threadPool.taskQueue.mutex);
                for(int j = 0; i < threadPool.threadnum; ++i){
                    pthread_join(threadPool.tidArr[j], NULL);
                }
                printf("main thread is closing\n");
                exit(0);
            }
        }
    }
    return 0;
}

